package view;
import java.awt.Color;
import java.awt.Point;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import java.awt.event.MouseMotionListener;

import javax.swing.*;
import javax.swing.border.BevelBorder;

import model.*;
public class MetaDeckFrame extends JFrame implements MouseMotionListener{
	
	final GameModel model;
	final TableComponent table; 
	
	/** used only when moving/dragging cards */
	CardStack inMotion = null;
	
	boolean dragging = false;
	
	
	
	public MetaDeckFrame() {
		final ImageLoader imageLoader = new ImageLoader();
		model = new GameModel();
		table = new TableComponent(model);
		
			
		final JPanel tablePanel = new JPanel();
		tablePanel.add(table);
		final JPanel eastPanel = new TableEastPanel();
		final JPanel westPanel = new TableWestPanel();
		final JPanel northPanel = new TableNorthPanel();
		
		
		
		HandComponent phand = new HandComponent(model, table, "SOUTH");
		HandComponent test = new HandComponent(model, table, "NORTH");
		final JPanel southPanel = new TableSouthPanel();
		southPanel.add(phand);
		southPanel.setBorder(BorderFactory.createBevelBorder(BevelBorder.RAISED));
		
		northPanel.add(test);
		northPanel.setBorder(BorderFactory.createBevelBorder(BevelBorder.RAISED));
		
		final JPanel sidePanel = new RightSidePanel();
		
		final JPanel centerRowPanel = new JPanel();
		centerRowPanel.add(westPanel);
		centerRowPanel.add(tablePanel);
		centerRowPanel.add(eastPanel);
		
		final JPanel gamePanel = new JPanel();
		gamePanel.setLayout(new BoxLayout(gamePanel, BoxLayout.PAGE_AXIS));
		gamePanel.add(northPanel);
		gamePanel.add(centerRowPanel);
		gamePanel.add(southPanel);
		
		gamePanel.addMouseListener(new PopClickListener(table, phand));
		
		gamePanel.addMouseMotionListener(this);
		addMouseMotionListener(this);
		
		//table.addMouseListener(new PopClickListener(table, phand));
		
		
		
		gamePanel.addMouseListener(new MouseListener() {

			@Override
			public void mouseClicked(MouseEvent arg0) {
				// TODO Auto-generated method stub
				
			}

			@Override
			public void mouseEntered(MouseEvent arg0) {
				// TODO Auto-generated method stub
				
			}

			@Override
			public void mouseExited(MouseEvent arg0) {
				// TODO Auto-generated method stub
				
			}

			@Override
			public void mousePressed(MouseEvent arg0) {
		
			int px = arg0.getLocationOnScreen().x;
				int py = arg0.getLocationOnScreen().y;
				if(containsPoint(table, px, py)) 
				{
					int mx = arg0.getXOnScreen()-table.getLocationOnScreen().x;
					int my = arg0.getYOnScreen()-table.getLocationOnScreen().y;
				
	
					
					CardStack stack = table.getStackAt(mx,my);
					Card card = table.getCardAt(mx, my);
					
					//double click on stack to highlight entire stack
					if (arg0.getClickCount() == 2 && stack != null)
					{
						System.out.println("highlighting entire stack " + stack.getSize());
	
						//highlight stack
						stack.highlightStack();
						table.repaint();
						
						
					}
					
					//single click on a card
					else if (arg0.getClickCount() == 1 && card != null 
							&& !card.isHighlighted() && arg0.getButton() == 1)
					{
						System.out.println("high one");
						model.unhighlightAllStacks();
						card.highlightedTrue();
						table.repaint();

					}
					else if (stack == null && arg0.getButton() == 1)
					{
						inMotion = null;
						model.cleanup();
						model.unhighlightAllStacks();
						table.repaint();
					}

				}
				
				model.cleanup();
				
			}
			
			@Override
			public void mouseReleased(MouseEvent arg0) {
				int px = arg0.getLocationOnScreen().x;
				int py = arg0.getLocationOnScreen().y;
		
				//mouse click release on empty spot
				if (arg0.getClickCount() != 2 && !dragging && inMotion != null)
				{
		
					inMotion = null;
					model.unhighlightAllStacks();
					table.repaint();
				}
				
				//mouse click release after drag
				if (dragging)
				{
	
					inMotion = null;
					dragging = false;
					
					
				}
				
				model.cleanup();

			}
			

			
		});
		
		JPanel content = new JPanel();
		content.add(gamePanel);
		content.add(sidePanel);
		add(content);
		pack();
		this.setTitle("MetaDeck");
		setDefaultCloseOperation(EXIT_ON_CLOSE);
		setVisible(true);
	}
	
	/**
	 * Utility function returning true if the component contains the screen coordinate point (x,y).
	 * The component API apparently doesn't have this function...
	 */
	public static boolean containsPoint(JComponent c, int x, int y) {
		Point p = c.getLocationOnScreen();
		return x>=p.x && x<p.x+c.getWidth() && y>=p.y && y<p.y+c.getHeight();
	}
	
	
	public void mouseMoved(MouseEvent e)
	{
		//System.out.println("mouse moved!");
		
	}
	
	/**
	 * move selected card around table
	 */
	public void mouseDragged(MouseEvent e)
	{
		dragging = true;
		
		int px = e.getLocationOnScreen().x;
		int py = e.getLocationOnScreen().y;
		//System.out.println("mouse dragged " + px + " " + py);
		
		int mx = e.getXOnScreen()-table.getLocationOnScreen().x;
		int my = e.getYOnScreen()-table.getLocationOnScreen().y;
	
		if (inMotion == null)
		{
			if(containsPoint(table, px, py)) 
			{		
				Card card = table.getCardAt(mx,my) ;
						
				CardStack stack = table.getStackAt(mx,my);
				
				if (stack != null)
				{
					
					if (stack.isHighlighted())
					{
						inMotion = stack;
						table.repaint();
					}
					else if (stack.isTopHighlighted())
					{
						inMotion = model.moveTopFromStack(stack, mx, my);
						table.repaint();
					}	
					
				}
				

			}	
			
		}
		else
		{
			inMotion.move(mx, my);
			table.repaint();
			
		}
		
		model.cleanup();
				
	}

	
	public static void main(String args[]) {
		new MetaDeckFrame();
	}
}
